package com.university.evaluation.controller;

import com.university.evaluation.common.ResponseResult;
import com.university.evaluation.entity.Appeal;
import com.university.evaluation.service.AppealService;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.media.Content;
import io.swagger.v3.oas.annotations.media.Schema;
import io.swagger.v3.oas.annotations.responses.ApiResponse;
import io.swagger.v3.oas.annotations.responses.ApiResponses;
import io.swagger.v3.oas.annotations.tags.Tag;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;

import java.util.List;
import java.util.Map;

@Slf4j
@RestController
@RequestMapping("/appeal")
@Tag(name = "申诉管理", description = "提供测评申诉的CRUD及相关操作API接口")
public class AppealController {

    @Autowired
    private AppealService appealService;

    @Operation(
        summary = "提交申诉",
        description = "学生提交测评结果申诉"
    )
    @ApiResponses({
        @ApiResponse(responseCode = "200", description = "提交成功", content = @Content(schema = @Schema(implementation = Appeal.class))),
        @ApiResponse(responseCode = "400", description = "提交失败", content = @Content(schema = @Schema(type = "string")))
    })
    @PostMapping
    @PreAuthorize("hasRole('STUDENT')")
    public ResponseResult<Appeal> submitAppeal(@RequestBody Appeal appeal) {
        try {
            log.info("学生提交申诉请求: studentId={}, scoreDetailId={}", appeal.getStudentId(), appeal.getScoreDetailId());
            boolean saveResult = appealService.save(appeal);
            if (saveResult) {
                log.info("申诉提交成功: appealId={}", appeal.getId());
                return ResponseResult.success("提交成功", appeal);
            } else {
                log.error("申诉提交失败");
                return ResponseResult.failure("提交失败");
            }
        } catch (Exception e) {
            log.error("提交申诉异常", e);
            return ResponseResult.failure("提交失败");
        }
    }

    @Operation(
        summary = "获取学生的申诉列表",
        description = "获取指定学生提交的所有申诉信息"
    )
    @GetMapping("/student/{studentId}")
    @PreAuthorize("hasRole('STUDENT') or hasRole('TEACHER') or hasRole('ADMIN')")
    public ResponseResult<List<Appeal>> getStudentAppeals(
            @Parameter(name = "studentId", description = "学生ID", required = true) 
            @PathVariable String studentId) {
        try {
            log.info("获取学生申诉列表请求: studentId={}", studentId);
            List<Appeal> appeals = appealService.findByStudentId(Long.valueOf(studentId));
            log.info("获取学生申诉列表成功: studentId={}, 共{}条记录", studentId, appeals.size());
            return ResponseResult.success("查询成功", appeals);
        } catch (Exception e) {
            log.error("获取学生申诉列表异常", e);
            return ResponseResult.failure("查询失败");
        }
    }

    @Operation(
        summary = "获取测评的申诉列表",
        description = "获取指定测评下的所有申诉信息"
    )
    @GetMapping("/evaluation/{evaluationId}")
    @PreAuthorize("hasRole('TEACHER') or hasRole('ADMIN')")
    public ResponseResult<List<Appeal>> getEvaluationAppeals(
            @Parameter(name = "evaluationId", description = "测评ID", required = true) 
            @PathVariable Long evaluationId) {
        try {
            log.info("获取测评申诉列表请求: evaluationId={}", evaluationId);
            // 暂时使用现有方法，需要后续在Service中实现findByEvaluationId方法
            List<Appeal> appeals = appealService.findByStatus("0"); // 临时使用查找待处理的申诉
            log.info("获取测评申诉列表成功: evaluationId={}, 共{}条记录", evaluationId, appeals.size());
            return ResponseResult.success("查询成功", appeals);
        } catch (Exception e) {
            log.error("获取测评申诉列表异常", e);
            return ResponseResult.failure("查询失败");
        }
    }

    @Operation(
        summary = "获取待处理的申诉列表",
        description = "获取所有状态为待处理的申诉信息"
    )
    @GetMapping("/pending")
    @PreAuthorize("hasRole('TEACHER') or hasRole('ADMIN')")
    public ResponseResult<List<Appeal>> getPendingAppeals() {
        try {
            log.info("获取待处理申诉列表请求");
            // 暂时使用现有方法，需要后续在Service中实现findPendingAppeals方法
            List<Appeal> appeals = appealService.findByStatus("0");
            log.info("获取待处理申诉列表成功: 共{}条记录", appeals.size());
            return ResponseResult.success("查询成功", appeals);
        } catch (Exception e) {
            log.error("获取待处理申诉列表异常", e);
            return ResponseResult.failure("查询失败");
        }
    }

    @Operation(
        summary = "处理申诉",
        description = "教师或管理员处理学生申诉"
    )
    @PutMapping("/{appealId}/process")
    @PreAuthorize("hasRole('TEACHER') or hasRole('ADMIN')")
    public ResponseResult<Void> processAppeal(
            @Parameter(name = "appealId", description = "申诉ID", required = true) 
            @PathVariable Long appealId, 
            @RequestBody Map<String, Object> processRequest) {
        try {
            log.info("处理申诉请求: appealId={}", appealId);
            String status = processRequest.get("status").toString();
            String remark = processRequest.get("remark").toString();
            Double newScore = processRequest.containsKey("newScore") ? Double.valueOf(processRequest.get("newScore").toString()) : null;
            boolean result = appealService.processAppeal(appealId, status, remark, newScore);
            if (!result) {
                return ResponseResult.failure("处理失败");
            }
            log.info("申诉处理成功: appealId={}", appealId);
            return ResponseResult.success("处理成功");
        } catch (Exception e) {
            log.error("处理申诉异常", e);
            return ResponseResult.failure("处理失败");
        }
    }

    @Operation(
        summary = "获取申诉详情",
        description = "获取指定申诉的详细信息"
    )
    @GetMapping("/{appealId}")
    @PreAuthorize("hasRole('STUDENT') or hasRole('TEACHER') or hasRole('ADMIN')")
    public ResponseResult<Appeal> getAppealById(
            @Parameter(name = "appealId", description = "申诉ID", required = true) 
            @PathVariable Long appealId) {
        try {
            log.info("获取申诉详情请求: appealId={}", appealId);
            Appeal appeal = appealService.getById(appealId);
            if (appeal != null) {
                log.info("获取申诉详情成功: appealId={}", appealId);
                return ResponseResult.success("查询成功", appeal);
            } else {
                log.warn("申诉不存在: appealId={}", appealId);
                return ResponseResult.failure("申诉不存在");
            }
        } catch (Exception e) {
            log.error("获取申诉详情异常", e);
            return ResponseResult.failure("查询失败");
        }
    }

    @Operation(
        summary = "更新申诉信息",
        description = "更新指定申诉的信息"
    )
    @PutMapping
    @PreAuthorize("hasRole('STUDENT') or hasRole('TEACHER') or hasRole('ADMIN')")
    public ResponseResult<Void> updateAppeal(@RequestBody Appeal appeal) {
        try {
            log.info("更新申诉信息请求: appealId={}", appeal.getId());
            boolean updateResult = appealService.updateById(appeal);
            if (updateResult) {
                log.info("更新申诉信息成功: appealId={}", appeal.getId());
                return ResponseResult.success("更新成功");
            } else {
                log.error("更新申诉信息失败");
                return ResponseResult.failure("更新失败");
            }
        } catch (Exception e) {
            log.error("更新申诉信息异常", e);
            return ResponseResult.failure("更新失败");
        }
    }

    @Operation(
        summary = "删除申诉",
        description = "删除指定申诉信息"
    )
    @DeleteMapping("/{appealId}")
    @PreAuthorize("hasRole('TEACHER') or hasRole('ADMIN')")
    public ResponseResult<Void> deleteAppeal(
            @Parameter(name = "appealId", description = "申诉ID", required = true) 
            @PathVariable Long appealId) {
        try {
            log.info("删除申诉请求: appealId={}", appealId);
            boolean deleteResult = appealService.removeById(appealId);
            if (deleteResult) {
                log.info("删除申诉成功: appealId={}", appealId);
                return ResponseResult.success("删除成功");
            } else {
                log.error("删除申诉失败");
                return ResponseResult.failure("删除失败");
            }
        } catch (Exception e) {
            log.error("删除申诉异常", e);
            return ResponseResult.failure("删除失败");
        }
    }
}